package com.ywu.application.standard.container.service;

import com.ywu.boot.exception.YwuRuntimeException;
import com.ywu.boot.utils.RedisUtils;
import com.ywu.common.gson.GsonUtils;
import com.ywu.application.standard.container.entity.PipeLineRedisEntity;
import com.ywu.application.standard.container.entity.step.Step;
import com.ywu.application.standard.container.entity.step.StepEntity;
import com.ywu.application.standard.container.entity.step.StepStatus;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;

import java.text.SimpleDateFormat;
import java.util.*;

/**
 * @ClassName PipeLineRedisService
 * @Description TODO
 * @Author GroundDemo
 * @Date 2024/4/13 15:41
 * @Version 1.0
 **/
@Service
@Slf4j
public class PipeLineRedisService {
    private static final String PIPE_LINE_REDIS_KEY_PREFIX = "YWU_PIPE_LINE_REDIS_KEY";

    /**
    * @Author GroundDemo
    * @Description 获取redis的key
    * @Date 15:52 2024/4/13
    * @Param [containerId]
    * @return java.lang.String
    **/
    private String getRedisKey(String containerId) {
        return PIPE_LINE_REDIS_KEY_PREFIX + ":" + containerId;
    }

    /**
    * @Author GroundDemo
    * @Description 获取当前时间格式化字符串
    * @Date 15:43 2024/4/13
    * @Param []
    * @return java.lang.String
    **/
    public String getCurrentTime() {
        SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        simpleDateFormat.setTimeZone(TimeZone.getTimeZone("Asia/Shanghai"));
        Date date = new Date();
        return simpleDateFormat.format(date);
    }

    /**
    * @Author GroundDemo
    * @Description 删除缓存中的entity数据
    * @Date 16:13 2024/4/13
    * @Param [containerId]
    * @return void
    **/
    public void deleteRedisKey(String containerId) {
        String redisKey = getRedisKey(containerId);
        RedisUtils.deleteByKey(redisKey);
    }

    /**
    * @Author GroundDemo
    * @Description 将流水线步骤对象存入redis缓存中
    * @Date 16:04 2024/4/13
    * @Param []
    * @return void
    **/
    public void setRedisEntity(PipeLineRedisEntity pipeLineRedisEntity, String containerId) {
        String redisKey = getRedisKey(containerId);
        RedisUtils.set(redisKey, GsonUtils.serialize(pipeLineRedisEntity));
    }

    /**
    * @Author GroundDemo
    * @Description 读取redis缓存中的信息并重新构建成entity对象
    * @Date 16:12 2024/4/13
    * @Param [containerId]
    * @return com.ywu.container.standard.entity.PipeLineRedisEntity
    **/
    public PipeLineRedisEntity getRedisEntity(String containerId) {
        String redisKey = getRedisKey(containerId);
        String entityJson = RedisUtils.getByKey(redisKey);
        return GsonUtils.deserialize(entityJson, PipeLineRedisEntity.class);
    }

    /**
    * @Author GroundDemo
    * @Description 构建git步骤step对象
    * @Date 15:48 2024/4/13
    * @Param [stepEntity, containerId]
    * @return void
    **/
    public void buildPullGitRedisInfo(StepEntity stepEntity, String containerId) {
        // 删除redis中的缓存
        deleteRedisKey(containerId);
        PipeLineRedisEntity pipeLineRedisEntity = new PipeLineRedisEntity();
        // 设置当前步骤为第一步
        pipeLineRedisEntity.setCurrentStep(1);
        // 创建一个新的map对象
        HashMap<Integer, Step> stepMap = new HashMap<>();
        // 构建Step对象
        Step step = new Step();
        // 设置子步骤
        step.setCurrentSonStep(1);
        // 构建出存储step详细信息的集合
        ArrayList<StepEntity> stepEntities = new ArrayList<>();
        if (stepEntity.getPipeLineStatus() == StepStatus.ERROR) {
            step.setStepStatus(StepStatus.ERROR);
            pipeLineRedisEntity.setPipeLineStatus(StepStatus.ERROR);
        } else {
            pipeLineRedisEntity.setPipeLineStatus(StepStatus.SUCCESS);
            step.setStepStatus(StepStatus.SUCCESS);
        }
        stepEntities.add(stepEntity);
        step.setStepEntities(stepEntities);
        // 将构建好的step对象存入map中
        stepMap.put(1, step);
        pipeLineRedisEntity.setStepMap(stepMap);
        // 存储redis缓存
        setRedisEntity(pipeLineRedisEntity, containerId);
        // 中断执行
        if (stepEntity.getPipeLineStatus() == StepStatus.ERROR) {
            throw new YwuRuntimeException("git pull error");
        }
    }

    /**
     * @Author GroundDemo
     * @Description 构建maven步骤step对象
     * @Date 15:48 2024/4/13
     * @Param [stepEntity, containerId, isEnd]
     * @return void
     **/
    public void buildMvnBuildInfo(StepEntity stepEntity, String containerId, Boolean isEnd) {
        // 获取redis缓存
        PipeLineRedisEntity redisEntity = getRedisEntity(containerId);
        // 设置当前步骤
        redisEntity.setCurrentStep(1);
        // 获取当前步骤的map
        Map<Integer, Step> stepMap = redisEntity.getStepMap();
        Step step = stepMap.get(1);
        // 构建stepEntity对象
        List<StepEntity> stepEntities = step.getStepEntities();
        step.setCurrentSonStep(2);
        if (isEnd) {
            step.setCurrentSonStep(3);
            stepEntities.remove(stepEntities.size() - 1);
        }
        stepEntities.add(stepEntity);
        if (stepEntity.getPipeLineStatus() == StepStatus.ERROR) {
            step.setStepStatus(StepStatus.ERROR);
            redisEntity.setPipeLineStatus(StepStatus.ERROR);
        } else {
            redisEntity.setPipeLineStatus(StepStatus.SUCCESS);
            step.setStepStatus(StepStatus.SUCCESS);
        }
        // 存储redis缓存
        setRedisEntity(redisEntity, containerId);
        // 中断执行
        if (stepEntity.getPipeLineStatus() == StepStatus.ERROR) {
            throw new YwuRuntimeException("mvn build error ");
        }
    }

    /**
     * @Author GroundDemo
     * @Description 构建推包步骤step对象
     * @Date 15:48 2024/4/13
     * @Param [stepEntity, containerId, isEnd]
     * @return void
     **/
    public void buildPushPackageInfo(StepEntity stepEntity, String containerId, Boolean isEnd) {
        // 获取redis缓存
        PipeLineRedisEntity redisEntity = getRedisEntity(containerId);
        // 设置当前步骤
        redisEntity.setCurrentStep(2);
        // 获取当前步骤的map
        Map<Integer, Step> stepMap = redisEntity.getStepMap();
        Step step = new Step();
        stepMap.put(2, step);
        // 构建stepEntity对象
        List<StepEntity> stepEntities = new ArrayList<>();
        stepEntities.add(stepEntity);
        step.setCurrentSonStep(1);
        step.setStepEntities(stepEntities);
        if (isEnd) {
            step.setCurrentSonStep(2);
        }
        if (stepEntity.getPipeLineStatus() == StepStatus.ERROR) {
            step.setStepStatus(StepStatus.ERROR);
            redisEntity.setPipeLineStatus(StepStatus.ERROR);
        } else {
            redisEntity.setPipeLineStatus(StepStatus.SUCCESS);
            step.setStepStatus(StepStatus.SUCCESS);
        }
        // 存储redis缓存
        setRedisEntity(redisEntity, containerId);
        if (stepEntity.getPipeLineStatus() == StepStatus.ERROR) {
            throw new YwuRuntimeException("push file error ");
        }
    }

    /**
    * @Author GroundDemo
    * @Description 构建部署步骤step对象
    * @Date 16:30 2024/4/13
    * @Param [stepEntity, containerId, isEnd]
    * @return void
    **/
    public void buildDeployContainer(StepEntity stepEntity, String containerId, Boolean isEnd) {
        // 获取redis缓存
        PipeLineRedisEntity redisEntity = getRedisEntity(containerId);
        // 设置当前步骤
        redisEntity.setCurrentStep(3);
        // 获取当前步骤的map
        Map<Integer, Step> stepMap = redisEntity.getStepMap();
        Step step = new Step();
        stepMap.put(3, step);
        // 构建stepEntity对象
        List<StepEntity> stepEntities = new ArrayList<>();
        stepEntities.add(stepEntity);
        step.setStepEntities(stepEntities);
        step.setCurrentSonStep(1);
        // 构建完成之后把步骤设置为4
        if (isEnd) {
            redisEntity.setCurrentStep(4);
            step.setCurrentSonStep(2);
        }
        if (stepEntity.getPipeLineStatus() == StepStatus.ERROR) {
            redisEntity.setCurrentStep(3);
            step.setStepStatus(StepStatus.ERROR);
            redisEntity.setPipeLineStatus(StepStatus.ERROR);
        } else {
            redisEntity.setPipeLineStatus(StepStatus.SUCCESS);
            step.setStepStatus(StepStatus.SUCCESS);
        }
        // 存储redis缓存
        setRedisEntity(redisEntity, containerId);
        if (stepEntity.getPipeLineStatus() == StepStatus.ERROR) {
            throw new YwuRuntimeException("docker restart container error");
        }
    }
}
